package com.wolfking.converter.rowmapper;

import com.google.common.collect.Maps;
import org.springframework.jdbc.core.RowMapper;

import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public abstract class AbstractCamelRowMapper<T> implements RowMapper<T> {
    @Override
    public T mapRow(ResultSet resultSet, int i) throws SQLException {

        ResultSetMetaData metaData = resultSet.getMetaData();
        int columnCount = metaData.getColumnCount();
        Map<String, Object> map = Maps.newHashMap();
        for (int j = 1; j < columnCount + 1; j++) {
            map.put(metaData.getColumnName(j), resultSet.getObject(metaData.getColumnName(j)));
        }

        for (int j = 1; j < columnCount + 1; j++) {
            String columnName = metaData.getColumnName(j);
            if (columnName.contains("_")) {
                Object resultSetObject = resultSet.getObject(columnName);
                columnName = lineToHump(columnName);
                map.computeIfAbsent(columnName, (k) -> resultSetObject);
            }
        }

        return convertMapToObject(map);
    }

    private static final Pattern linePattern = Pattern.compile("_(\\w)");

    /**
     * 下划线转驼峰
     */
    public static String lineToHump(String str) {
        if (!str.contains("_")) {
            return str;
        }
        StringBuffer sb = new StringBuffer();
        Matcher matcher = linePattern.matcher(str);
        while (matcher.find()) {
            matcher.appendReplacement(sb, matcher.group(1).toUpperCase());
        }
        matcher.appendTail(sb);
        return sb.toString();
    }

    protected abstract T convertMapToObject(Map<String, Object> map);
}
